<template>
  <div class="custom-properties-panel">
    <el-form ref="form" :model="formData" label-width="80px">
      <div class="empty" v-if="element === null">暂不支持该类型配置</div>
      <div v-else>
        <el-tabs type="border-card">
          <el-tab-pane v-for="(item,i) in panelConfig" :key="i" :label="item.name">
            <div v-for="(group,i) in item.groups" :key="i">
              {{ group.name }}
              <br/>
              <div v-for="(field,i) in group.fields" :key="i">
                <el-form-item :label="field.desc + ':'" v-if="handlerField(field)" label-width="100px">
                  <el-select v-if="field.type === 'select' && handlerField(field)" placeholder="请选择"
                             v-model="formData[currentFormKey][currentId][field.name]" value-key="key"
                             @change.native="changeField($event,field.name,field.isSyncBpmn)">
                    <el-option v-for="item in handlerDefaultValue(field.defaultValue,[])" :key="item.key"
                               :label="item.name" :value="item.key"></el-option>
                  </el-select>
                  <el-input v-else
                            v-model="formData[currentFormKey][currentId][field.name]" :readonly="field.readOnly"
                            @change.native="changeField($event,field.name,field.isSyncBpmn)">
                  </el-input>
                </el-form-item>
              </div>
            </div>
          </el-tab-pane>
        </el-tabs>
      </div>
    </el-form>
  </div>
</template>
<script>
import PropertiesPanelConfig from "@/components/Workflow/CustomPropertiesPanel/config";
import config from "@/components/Workflow/CustomPropertiesPanel/config/custom/properties";
import ElInput from 'element-ui/packages/input'

export default {
  name: 'PropertiesPanel',
  components: {ElInput},
  props: {
    modeler: {
      type: Object,
      default: () => ({})
    }
  },
  data() {
    return {
      element: null, // 当前点击的元素
      panelConfig: [],  // 面板字段配置信息
      currentFormKey: null, // 当前表单的key,用于区分不同类型节点的表单数据
      formData: {}, // 整个流程图配置的表单数据
      propertiesPanelConfig: null, // 所有的配置信息
      currentId: null, // 当前操作的流程节点对象ID
      temp:{}
    }
  },
  created() {
    this.init()
    this.propertiesPanelConfig = new PropertiesPanelConfig("custom", config)
  },
  methods: {
    init() {
      const {modeler} = this
      let eventBus = modeler.get("eventBus");
      eventBus.on(["shape.remove", "connection.remove"], e => {
        let element = e.element;
        if (this.element) {
          this.element = null
          this.showRootElementPanel()
        }
        let configByElementType = this.propertiesPanelConfig.getConfigByElementType(element.type);
        if (configByElementType) {
          delete this.formData[configByElementType.formKey][element.id];
        }
      })
      eventBus.on(["element.click", "connection.added", "shape.changed"], e => {
        if (!this.changeElementConfig(e.element)) {
          this.element = null;
          return;
        }
        if ('connection.added' === e.type) {
          // 初始化element属性到表单当中
          this.addElementFormField(e.element)
          // 此处调用是为了把数据同步到父组件
          this.changeField()
          return;
        }
        // 初始化element属性到表单当中
        this.addElementFormField(e.element)
        // 此处调用是为了把数据同步到父组件
        this.changeField()
      })
      eventBus.on("import.done", e => {
        let {error} = e;
        if (error) {
          console.log(error)
        }
        this.showRootElementPanel()
      })
    },
    showRootElementPanel() {
      let rootElement = this.getRootElement();
      this.changeElementConfig(rootElement)
      // 初始化element属性到表单当中
      this.addElementFormField(rootElement)
      // 此处调用是为了把数据同步到父组件
      this.changeField();
    },
    changeElementConfig(element) {
      let type = element.type;
      let configByElementType = this.propertiesPanelConfig.getConfigByElementType(type)
      if (configByElementType) {
        this.currentId = element.id
        this.element = element
        this.panelConfig = configByElementType.tab;
        this.currentFormKey = configByElementType.formKey
        return true;
      }
      console.log("未适配类型: " + type)
      return false;
    },
    updateProperties(properties) {
      const {modeler, element} = this
      const modeling = modeler.get('modeling')
      modeling.updateProperties(element, properties)
    },
    addElementFormField(element) {
      let businessObject = element.businessObject;
      let elFormData = this.formData[this.currentFormKey] ? this.formData[this.currentFormKey] : {}
      let id = businessObject.get("id");
      let name = businessObject.get("name");
      let type = element.type;
      if (Object.keys(elFormData).length === 0) {
        elFormData[id] = {
          id: id,
          name: name,
          _type: type
        }
        this.$set(this.formData, this.currentFormKey, elFormData)
      } else {
        this.$set(elFormData, id, {
          id: id,
          name: name,
          _type: type
        });
      }
    },
    changeField(event, type, isSync = false) {
      if (!event || !type) {
        this.$emit("setFormData", this.formData);
        return;
      }
      if (isSync) {
        this.$emit("setFormData", this.formData);
        const value = event.target.value
        let properties = {}
        properties[type] = value
        this.element[type] = value
        this.updateProperties(properties) // 调用属性更新方法
      }
    },
    getRootElement() {
      let elementRegistry = this.modeler.get('elementRegistry');
      let process = elementRegistry.filter(d => {
        return d.type && d.type === 'bpmn:Process'
      });
      if (process && process.length > 0) {
        return process[0];
      }
      return null
    },
    /**
     * 处理字段配置
     */
    handlerField(field) {
      if (field.isShow && !field.isShow(this.element)) {
        return false;
      }
      if (field.dependOn) {
        let formDatumElementElement = this.formData[this.currentFormKey][this.currentId][field.dependOn.field];
        if (formDatumElementElement === field.dependOn.value) {
          return true;
        } else {
          return false;
        }
      }
      return true;
    },
    /**
     * 默认值处理
     * @param val
     * @param def
     */
    handlerDefaultValue(val,def){
      if(val){
        if(typeof val === "function" && typeof val.nodeType !== "number"){
          let call = val.call(this);
          if(call){
            return call;
          }
        }
        return val;
      }
      return def;
    },
    validate() {
      // 校验表单数据
      return false;
    }
  }
}
</script>
<style>
.custom-properties-panel {
  position: absolute;
  right: 0;
  top: 0;
  width: 100%;
  background-color: #fff9f9;
  border-color: rgba(0, 0, 0, 0.09);
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.09);
}

/*.custom-properties-panel .el-input input:read-only,.custom-properties-panel textarea:read-only {*/
/*  background-color: #efefef;*/
/*}*/

</style>
